#include <iostream>
#include <signal.h>
#include <unistd.h>
#include <sys/types.h>
#include <unistd.h>

void hanlder(int signumber)
{
    std::cout  << signumber << "信号递达" <<std::endl;

}

void print(sigset_t pendin)
{
    std::cout << "pid_t:" << getpid() << "; ";
    for(int i=31;i >= 1;i--)
    {

        if(sigismember(&pendin,i))  //用于判断信号集是否包含某种信号，包含返回1
        {
            std::cout << 1;
        }
        else
        {
            std::cout << 0;

        }
        
    }
    std::cout << std::endl;
}


/********************** 代码整体思路 *******************************
 捕获信号2  ->  创建两个信号集(old_set用于保存旧的信号集)
 对两个信号集合进行清空  ->  对block_set表写入信号2
 调用sigprocmask 把block表清空，清空之前把数据存放到了old表

 15秒之后对信号2解除屏蔽  把进程的block表更改成之前保存的old表(这样就实现了对信号2的解除)


*****************************************************/


int main()
{

    int cnt = 0;
    signal(2,hanlder);


    sigset_t block_set,old_set;

    
    //对两个表进行初始化
    sigemptyset(&block_set);
    sigemptyset(&old_set);
    print(block_set);

    sigaddset(&block_set,2); //将信号2添加到block_set表中   只是对 block_set 这一变量进行修改，并没有修改到当前进程的block内核里
    std::cout << "sigaddset" << std::endl;
    print(block_set);

    sigprocmask(SIG_BLOCK,&block_set,&old_set);  //修改当前进程的block内核表，对信号2进行了屏蔽
    std::cout << "sigprocmask" <<std::endl;
    print(block_set);


    while(true)
    {
        
        sigset_t pendin;
        sigpending(&pendin);
        print(pendin);
        cnt++;
        if(cnt > 15 )
        {
            std::cout << "解除对2号的屏蔽" << std::endl;
            sigprocmask(SIG_SETMASK,&old_set,&block_set);


            // sleep(5);
            // sigprocmask(SIG_SETMASK,&block_set,&old_set);
            // cnt = 5;
        }
        sleep(1);
    }






    /***********************************************
    while(true)
    {
        # 通过测试可以得出，sigaddset并没有添加到当前进程内核信号集中，我们运行 ctrl+c依旧可以执行，并没有被屏蔽

        sigaddset(&block_set,2); //将信号2添加到block_set表中   只是对 block_set 这一变量进行修改，并没有修改到当前进程的block内核里

        # 通过测试可以得出，sigprocmask 已修改当前进程的信号集表，运行之后 ctrl+c 不能够执行
        sigprocmask(SIG_BLOCK,&block_set,&old_set);  //修改当前进程的block内核表，对信号2进行了屏蔽
        std::cout << "***********" << std::endl;
        sleep(1);
    }
    **************************************************/



   // sigaddset(&block_set,2); //将信号2添加到block_set表中   只是对 block_set 这一变量进行修改，并没有修改到当前进程的block内核里
   // print(block_set);

    //sigprocmask(SIG_BLOCK,&block_set,&old_set);  //修改当前进程的block内核表，对信号2进行了屏蔽
    //print(block_set);





    return 0;
}